package com.hkzhao.reportingsystem.service.impl;

import com.github.pagehelper.PageHelper;
import com.hkzhao.reportingsystem.common.api.CommonResult;
import com.hkzhao.reportingsystem.common.utils.JwtTokenUtil;
import com.hkzhao.reportingsystem.common.utils.TranslateToToken;
import com.hkzhao.reportingsystem.component.AuthCaseSender;
import com.hkzhao.reportingsystem.component.VerifyFailedReceiver;
import com.hkzhao.reportingsystem.component.VerifyFailedSender;
import com.hkzhao.reportingsystem.component.VerifySuccessSender;
import com.hkzhao.reportingsystem.dto.CaseDto;
import com.hkzhao.reportingsystem.mbg.mapper.*;
import com.hkzhao.reportingsystem.mbg.model.*;
import com.hkzhao.reportingsystem.service.DoctorService;
import com.hkzhao.reportingsystem.service.MangerService;
import com.hkzhao.reportingsystem.service.RedisTmpService;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.data.domain.Page;
import org.springframework.security.authentication.BadCredentialsException;
import org.springframework.security.authentication.UsernamePasswordAuthenticationToken;
import org.springframework.security.core.AuthenticationException;
import org.springframework.security.core.context.SecurityContextHolder;
import org.springframework.security.core.userdetails.UserDetails;
import org.springframework.security.core.userdetails.UserDetailsService;
import org.springframework.security.crypto.password.PasswordEncoder;
import org.springframework.stereotype.Service;

import javax.servlet.http.HttpServletRequest;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;
import java.util.Set;

@Service
public class ManagerServiceImpl implements MangerService {
    private final static Logger LOGGER = LoggerFactory.getLogger(ManagerServiceImpl.class);
    @Autowired(required = false)
    private ManagerMapper managerMapper;
    @Autowired(required =false)
    private UserDetailsService userDetailsService;
    @Autowired
    private JwtTokenUtil jwtTokenUtil;
    @Autowired
    private PasswordEncoder passwordEncoder;
    @Autowired(required = false)
    private NewsMapper newsMapper;
    @Autowired(required = false)
    private DoctorMapper doctorMapper;
    @Autowired(required = false)
    private VerifySuccessSender verifySuccessSender;
    @Autowired(required = false)
    private DoctorService doctorService;
    @Autowired(required = false)
    private VerifyFailedSender verifyFailedSender;
    @Autowired(required = false)
    private AdminuserMapper adminuserMapper;
    @Autowired(required = false)
    private UserPermissionMapper userPermissionMapper;
    @Value("${jwt.doctorAuthority}")
    private String doctorAuthority;
    @Value("${redis.key.casePrefix.authCode}")
    private String redis_auth_Case_key;
    @Autowired
    private RedisTmpService redisTmpService;
    @Autowired(required = false)
    private CaseMapper caseMapper;
    @Autowired
    private AuthCaseSender authCaseSender;
    @Override
    public String login(String username, String password) {
        String token = null;
        try{
            UserDetails userDetails = userDetailsService.loadUserByUsername(username);
            if(!passwordEncoder.matches(password,userDetails.getPassword()))
            {
                throw new BadCredentialsException("密码不正确");
            }
            UsernamePasswordAuthenticationToken authenticationToken =
                    new UsernamePasswordAuthenticationToken(userDetails,null,userDetails.getAuthorities());
            SecurityContextHolder.getContext().setAuthentication(authenticationToken);
            token = jwtTokenUtil.generateToken(userDetails);
        }catch (AuthenticationException e){
            LOGGER.warn("登录异常:{}",e.getMessage());
        }
        return token;
    }

    @Override
    public CommonResult addNews(String title, String text, HttpServletRequest request) {
        String username = new TranslateToToken().GetUsernameByHeader(request);
        if(username.length()==0)
            return CommonResult.failed("用户名不能为空");
        String uuid = TranslateToToken.GetGUID();
        Date date = new Date();
        News news = new News();
        news.setCreateTime(date);
        news.setNewsId(uuid);
        news.setText(text);
        news.setTitle(title);
        news.setManageTokenId(managerMapper.selectByPrimaryKey(username).getManagerTokenId());
        newsMapper.insert(news);
        return CommonResult.success(uuid,"陈坤插入新闻");
    }

    @Override
    public CommonResult verifyFailed(String username) {
        doctorMapper.deleteByPrimaryKey(username);
        long time = 300;
        verifyFailedSender.sendMessage(username,time);
        return CommonResult.success(username,"审核失败已经删除");
    }

    @Override
    public CommonResult verifyFailedSendEamil(String username) {
        doctorService.send_email(username,"对不起您的用户名为："+username+"  审核失败，请重新提交注册");
        return CommonResult.success(username,"该用户审核失败");
    }

    @Override
    public CommonResult verifySuccess(String username) {
        Doctor doctor = doctorMapper.selectByPrimaryKey(username);
        doctor.setStatus(1);
        Adminuser adminuser = new Adminuser();
        adminuser.setTokenId(doctor.getDoctorTokenId());
        adminuser.setUsername(doctor.getUsername());
        adminuser.setPosition("0"); //代表医生
        UserPermission userPermission = new UserPermission();
        userPermission.setCreateTime(new Date());
        userPermission.setTokenId(doctor.getDoctorTokenId());
        userPermission.setValue(doctorAuthority);
        doctorMapper.updateByPrimaryKey(doctor);
        adminuserMapper.insert(adminuser);
        userPermissionMapper.insert(userPermission);
        long time = 300;
        verifySuccessSender.sendMessage(username,time);
        return CommonResult.success(username,"该用户审核陈坤");
    }

    @Override
    public CommonResult verifySuccessSendEmail(String username) {
        doctorService.send_email(username,"恭喜你，用户名为："+username+"经审核通过，该账户可以使用！");
        return CommonResult.success(username,"该用户审核成功");
    }

    @Override
    public List<Doctor> getNeedVerifyDoctor(int pageNum, int pageSize) {
        PageHelper.startPage(pageNum,pageSize);
        DoctorExample doctorExample = new DoctorExample();
        doctorExample.createCriteria().andStatusEqualTo(0);
        return doctorMapper.selectByExample(doctorExample);
    }
//不知道这个分页有没有用
    @Override
    public List<CaseDto> getAllAuthCase(int pageNum, int pageSize) {
        PageHelper.startPage(pageNum,pageSize);
        Set<Object> caseDtoSet = redisTmpService.sMembers(redis_auth_Case_key);
        List<CaseDto> list = new ArrayList<>();
        for (Object o :caseDtoSet) {
            list.add((CaseDto) o);
        }
        return list;
    }
    private CommonResult modifyCaseSuccess(CaseDto caseDto){
        Case c  =  caseMapper.selectByPrimaryKey(caseDto.getCaseId());
        c.setLocate(caseDto.getLocate());c.setGender(caseDto.getGender());c.setDiseaseType(caseDto.getDiseaseType());
        c.setLevel(caseDto.getLevel());c.setAge(caseDto.getAge());c.setTelephone(caseDto.getTelephone());
        c.setNote(caseDto.getNote());c.setTime(caseDto.getTime());
        caseMapper.updateByPrimaryKey(c);
        redisTmpService.sRemove(redis_auth_Case_key,caseDto);
        modifyEmailSender("案件："+c.getCaseId()+" 经审核通过修改",c.getCaseId(),c.getDoctorTokenId());
        return CommonResult.success(caseDto.getCaseId(),"成功修改案例具体信息");

    }
    private boolean modifyEmailSender(String state,String caseid,String doctor_token_id)
    {
        DoctorExample d = new DoctorExample();
        d.createCriteria().andDoctorTokenIdEqualTo(doctor_token_id);
        List<Doctor> list = doctorMapper.selectByExample(d);
        if(list!=null&&list.size()>0)
        {
            String username = list.get(0).getUsername();
            long time = 60;
            authCaseSender.sendMessage(new String[]{username,caseid,state},time);
            return true;
        }
        return false;
    }
    @Override
    public CommonResult authCaseSuccessOrFailed(String case_token_id, String target) {
        Set<Object> caseSet = redisTmpService.sMembers(redis_auth_Case_key);
        for (Object o:caseSet) {
            if(((CaseDto)o).getCaseId().equals(case_token_id))
            {
                if(target.equals("1")) //成功
                {
                    return modifyCaseSuccess((CaseDto)o);
                }
                else  if(target.equals("0"))//失败
                {
                    redisTmpService.sRemove(redis_auth_Case_key,o);//删掉
                    modifyEmailSender("案件："+((CaseDto)o).getCaseId()+" 经审核不通过修改",((CaseDto)o).getCaseId(),((CaseDto)o).getDoctorTokenId());
                    return CommonResult.success(case_token_id,"删除成功");
                }
                else
                {
                    return CommonResult.failed("target不存在或者不为0和1");
                }
            }
        }
        return CommonResult.failed("caseId不存在");
    }

    @Override
    public CommonResult sendAuthCaseInformEmail(String[] username_caseid_state) {
        doctorService.send_email(username_caseid_state[0],"案件： "+username_caseid_state[1]
        +",审核结果: "+username_caseid_state[2]);
        return CommonResult.success(username_caseid_state[0],"成功发送邮件");
    }
}
